package com.scalar.chiptrack.adaptor.kyec;

import com.scalar.chiptrack.jobs.JobHandler;
import com.scalar.chiptrack.adaptor.AdaptorConstants;
import com.scalar.chiptrack.adaptor.InventoryLot;
import com.scalar.chiptrack.adaptor.TestLot;
import com.scalar.chiptrack.adaptor.AdaptorUtils;
import com.scalar.chiptrack.adaptor.ShippedLot;
import com.scalar.chiptrack.adaptor.utils.ParserResult;
import com.scalar.chiptrack.adaptor.utils.Parser;
import com.scalar.chiptrack.adaptor.utils.ParserFactory;
import com.scalar.chiptrack.adaptor.utils.XLSParserImpl;
import com.scalar.chiptrack.adaptor.dao.InventoryLotDAO;
import com.scalar.chiptrack.adaptor.dao.ShippedLotDAO;
import com.scalar.chiptrack.adaptor.dao.TestAdaptorDAO;
import com.scalar.chiptrack.adaptor.dao.AdaptorDAO;
import com.scalar.chiptrack.adaptor.dao.AdaptorRunInfo;
import com.scalar.chiptrack.utils.Logger;
import com.scalar.chiptrack.utils.StringUtils;
import com.scalar.chiptrack.db.DBTransaction;
import com.scalar.ScalarException;

import java.io.File;
import java.util.ArrayList;
import java.util.HashMap;


public class KYECDataParser extends JobHandler implements AdaptorConstants
{

    private HashMap<String, InventoryLot> m_fgDataMap    = new HashMap<String, InventoryLot>();
    private HashMap<String, ShippedLot> m_fgshipDataMap  = new HashMap<String, ShippedLot>();
    private HashMap<String, TestLot> m_testDataMap       = new HashMap<String, TestLot>();

    private Logger m_parserLogger       = null;
    private String m_dataOutputDir      = null;

    public  KYECDataParser() throws ScalarException
    {
        try
        {
            m_dataOutputDir = AdaptorUtils.getDataOutputDir( VENDOR_NAME_KYEC , WIP_TYPE_TEST );

            if ( m_dataOutputDir != null )
            {
                AdaptorUtils.makeAllAdaptorDirs( m_dataOutputDir );

                m_parserLogger= AdaptorUtils.getDataParserLogger( m_dataOutputDir,VENDOR_NAME_KYEC );

                AdaptorUtils.setLogger( m_parserLogger );
                ShippedLotDAO.setLogger( m_parserLogger);
                InventoryLotDAO.setLogger(m_parserLogger);
                TestAdaptorDAO.setLogger( m_parserLogger);
            }
        }
        catch ( Exception se )
        {
            log( "ERROR!! ERROR!! ERROR!! Exception while loading KYEC output directory details from database, Exception: " + se );
            System.out.println( "ERROR!! ERROR!! ERROR!! Exception while loading KYEC output directory details from database, Exception: " + se );
        }
    }
    public static void main( String args[] ) throws Exception
    {
        try
        {
            new KYECDataParser().execute();
        }
        catch ( Exception e )
        {
            throw e;
        }
    }
    public void execute() throws Exception
    {
        AdaptorUtils.printHeader( VENDOR_NAME_KYEC, CONSTANT_PARSER );

        File doneDestDir = new File( m_dataOutputDir + "/done" );
        File dataoutDir  = new File( m_dataOutputDir );

        File[] fileList = dataoutDir.listFiles();

        if ( ( fileList == null ) || (fileList.length <= 3))
        {
            log("No file found in directory: " + dataoutDir);
            System.out.println("No file found in directory: " + dataoutDir );
            throw new ScalarException("No file found in directory: " + dataoutDir+ "----\n\n" );
        }

        ArrayList<File> successFileList = new ArrayList<File>();

        boolean success = false;

        for ( int i = 0; i < fileList.length; i++ )
        {
            if ( fileList[i].isDirectory() == true )
            {
                continue;
            }

            try
            {
                 if ( fileList[i].getName().startsWith( KYECAdaptor.FILE_NAME_FT_WIP )  || fileList[i].getName().indexOf( KYECAdaptor.FILE_NAME_FT_WIP )  != -1)
                {
                     parseTestWipReport( fileList[i].getAbsolutePath() );

                    successFileList.add(fileList[i]);
                }
                if ( fileList[i].getName().startsWith( KYECAdaptor.FILE_NAME_FT_SHIP ) )
                {
                    //parseTestShipSheet( fileList[i].getAbsolutePath() );

                    successFileList.add(fileList[i]);
                }
                success = true;
            }
            catch (Exception e)
            {
                success = false;
                log("Exception while parsing file: " + fileList[i].getAbsolutePath() + "\nException: " + e);
                e.printStackTrace();
                throw e;
            }
        }

        DBTransaction dbTransaction = null;

		 try
        {
           // Saving FINAL TEST Information
           if ( m_testDataMap.isEmpty() == false )
            {
                log( " Updating Test Lot Information" );
                TestAdaptorDAO.saveTestLot( dbTransaction,m_testDataMap.values().iterator(), LOCATION_TYPE_FT, VENDOR_NAME_KYEC );
            }
            else
           {
               TestAdaptorDAO.closeTestLot( dbTransaction, LOCATION_TYPE_FT, VENDOR_NAME_KYEC );
           }

           success = true;
        }
        catch ( ScalarException se )
        {
            success = false;
            se.printStackTrace();
            log( "ERROR!! ERROR!! ERROR!! Could not update Test Lot information into database: " + se );
            throw se;
        }

         // to save the Finished Goods lot tables
       try
       {
           if ( m_fgDataMap.isEmpty() == false )
           {
               log(" Updating Finished Goods Lot Information");
               InventoryLotDAO.saveInventoryLot( null, m_fgDataMap.values().iterator(), LOCATION_TYPE_FG, VENDOR_NAME_KYEC );
               success = true;
           }
           else
           {
               InventoryLotDAO.closeInventoryLot(null, LOCATION_TYPE_FG, VENDOR_NAME_KYEC );
           }
      }
      catch (ScalarException se)
      {
          success = false;
          se.printStackTrace();
          log("ERROR!! ERROR!! ERROR!! Could not update Finished Goods Lot information into database: " + se);
          throw se;
      }

        try
        {
            if (m_fgshipDataMap.isEmpty() == false)
            {
                log("Updating FG Shipment Information");
                ShippedLotDAO.saveShippedLot( dbTransaction, m_fgshipDataMap.values().iterator());
            }
            success = true;
        }
        catch (Exception e)
        {
            success = false;
            log("ERROR!! ERROR!! ERROR!! Could not update KYEC FG Shipping information into database: " + e);
            e.printStackTrace();
            throw e;
        }

        // TO SEND THE NEW LOTS, NEW TRANSIT LOTS, NO PO LOTS, DISCREPANCY LOTS NOTIFICATIONS TO THE USER
        AdaptorDAO.sendAllNotifications( VENDOR_NAME_KYEC,true, true, true );

        // To Close the Drop Out Lots
        AdaptorDAO.closeDropOutLots( VENDOR_NAME_KYEC );

        int adaptor_id = AdaptorRunInfo.getLastRunAdaptorId( KYECAdaptor.ADAPTOR_NAME, CONSTANT_ADAPTOR);
        // transaction 9
        try
        {
            if (success)
            {
                //AdaptorRunInfo.saveAdaptorLastUpdatedStatus(KYECAdaptor.ADAPTOR_NAME, CONSTANT_SUCCESS);
                AdaptorRunInfo.saveAdaptorLastUpdatedStatus(CONSTANT_PARSER, KYECAdaptor.ADAPTOR_NAME, CONSTANT_SUCCESS, adaptor_id);
                System.out.println("SUCCESSFULLY UPDATED IN THE DATABASE");
            }
        }
        catch (ScalarException se)
        {
            success = false;  //As filES DATA SAVED , UPDATEING AS SUCCESS
            AdaptorRunInfo.saveAdaptorLastUpdatedStatus(CONSTANT_PARSER, KYECAdaptor.ADAPTOR_NAME, CONSTANT_SUCCESS, adaptor_id);
            log("WARNING!! WARNING!! WARNING!! Could not update Adaptor run information, Exception: " + se);
            throw se;
        }
       
        // Step 10
        // Move the successful files to 'done' directory
        if (success)
        {
            AdaptorUtils.moveFilesToDone( successFileList, doneDestDir);
        }
    }

    private void parseTestWipReport (String fileName ) throws Exception
    {
        if ( fileName == null ) throw new ScalarException( "Filename argument is null" );

        ParserResult result            = null;

        InventoryLot inventoryLot  = null;
        TestLot      testLot       = null;
        String partNumber       = null;
        String fabLotNumber     = null;
        String vendorLotNumber  = null;
        int dieQtyIn            = 0;
        String dateIn           = null;


        try
        {
            File detailWipFile = new File( fileName );
            if ( !detailWipFile.exists() )
            {
                throw new ScalarException( fileName + " doesnt exist" );
            }

            Parser parser = ParserFactory.getXLSParser( detailWipFile );

            ((XLSParserImpl)parser).setHeaderRowIdx(4);
            ((XLSParserImpl)parser).setDataStartRowIdx(5);

            log( "\nFound " + fileName );
            log( "\nParsing the file for LFT Wip Report..." );
            System.out.println( "\nFound " + fileName );
            System.out.println( "\nParsing the file for LFT Wip Report..." );

            result = parser.parse();

            while ( result.next() )
            {                   
                partNumber      = result.getString("DEVICE");
                fabLotNumber    = result.getString("Lot_No");
                vendorLotNumber = result.getString("Lot_InNo");
                if ( vendorLotNumber == null )
                {
                    vendorLotNumber = fabLotNumber;
                }
                if ( partNumber != null && partNumber.trim().length() > 0 && fabLotNumber != null && fabLotNumber.trim().length() > 0 )
                {
                    try
                    {
                        dieQtyIn = result.getInt("Current_Qty") ;
                    }
                    catch(NumberFormatException nfe)
                    {
                        dieQtyIn = 0;
                    }

                    if ( dieQtyIn > 0 )
                    {
                        if ( result.getString( "IN_Date") != null )
                        {
                            dateIn = StringUtils.formatDate( result.getString( "IN_Date"), "yyyy/MM/dd HH:mm:ss", "MM/dd/yyyy HH:mm:ss" );
                        }
                        else if ( result.getString( "RCV_Date") != null )
                        {
                            dateIn = StringUtils.formatDate( result.getString( "RCV_Date"),"yyyy/MM/dd HH:mm:ss", "MM/dd/yyyy HH:mm:ss" );
                        }

                        if ( result.getString("Status") != null
                                && ( "FGI".equalsIgnoreCase( result.getString("Status").trim() )  || ( "FINISH".equalsIgnoreCase( result.getString("Status").trim() ) && "INV".equalsIgnoreCase(result.getString("Step").trim() ) ) ) )
                        {
                            log("IN FG lotNumber = " + vendorLotNumber);
                            inventoryLot = m_fgDataMap.get( vendorLotNumber + fabLotNumber + partNumber );

                            if( inventoryLot == null )
                            {
                                inventoryLot = new InventoryLot( VENDOR_NAME_KYEC,  LOCATION_TYPE_FG);
                                m_fgDataMap.put( vendorLotNumber + fabLotNumber + partNumber , inventoryLot );
                            }

                            inventoryLot.setPartNumber( partNumber );
                            inventoryLot.setLotNumber( vendorLotNumber );
                            inventoryLot.setFabLotNumber( fabLotNumber );
                            inventoryLot.setQtyIn( dieQtyIn+"" );
                            inventoryLot.setDateIn( dateIn );
                            inventoryLot.setStatus(LOT_STATUS_RUNNING);
                            if ("ENG".equalsIgnoreCase(result.getString("LotType")) )
                            {
                                inventoryLot.setLotCategory( LOT_CATEGORY_TYPE_ENGG );
                            }
                            else if ("RMA".equalsIgnoreCase( result.getString("LotType") ) )
                            {
                                  inventoryLot.setLotCategory( LOT_CATEGORY_TYPE_RMA );
                            }
                            else
                            {
                                inventoryLot.setLotCategory( LOT_CATEGORY_TYPE_PROD );
                            }
                            inventoryLot.setDateCode( result.getString("DateCode") );
                            inventoryLot.setPkgType( result.getString("Package Type") );
                        }
                        else
                        {
                            log("In FT" + vendorLotNumber );
                            testLot = m_testDataMap.get( vendorLotNumber + fabLotNumber + partNumber);

                            if (testLot == null)
                            {
                                testLot = new TestLot( VENDOR_NAME_KYEC);
                                m_testDataMap.put( vendorLotNumber + fabLotNumber + partNumber, testLot);
                            }

                            testLot.setQtyIn( dieQtyIn+"" );
                            testLot.setLotNumber( vendorLotNumber );
                            testLot.setPartNumber( partNumber );
                            if ( "HOLD".equalsIgnoreCase(result.getString("Status") ) )
                            {
                                testLot.setStatus( LOT_STATUS_HOLD );
                            }
                            else
                            {
                                testLot.setStatus( LOT_STATUS_RUNNING );
                            }
                            testLot.setFabLotNumber( fabLotNumber );
                            testLot.setPackageType( result.getString("Package Type") );
                            testLot.setDateCode( result.getString("DateCode") );
                            testLot.setPsType( LOCATION_TYPE_FT );
                            testLot.setStage( result.getString("Step") );
                            if ( "ENG".equalsIgnoreCase(result.getString("LotType")))
                            {
                                testLot.setCategory ( LOT_CATEGORY_TYPE_ENGG );
                            }
                            else if ("RMA".equalsIgnoreCase( result.getString("LotType") ))
                            {
                                 testLot.setCategory( LOT_CATEGORY_TYPE_RMA );
                            }
                            else
                            {
                                testLot.setCategory( LOT_CATEGORY_TYPE_PROD );
                            }
                            testLot.setDateIn( dateIn );

                        }
                    }
                }

            }
        }
        catch(Exception e )
        {
            e.printStackTrace();
            throw e;
        }
    }

   /* public void getTestShipDetails(ArrayList testShipList) throws Exception
    {
       if ( testShipList == null || testShipList.size() == 0 )
       {
            return;
       }
       KYECAssyShippingInfo testShipInfo= null;
       String partNumber                = null;
       String lotNumber                 = null;
       ShippedLot testShippedLot        = null;
       String fabLotNumber              = null;
       String nextLocation              = null;

       try
       {
           Iterator iterator = testShipList.iterator();

           while ( iterator.hasNext() )
           {
               testShipInfo = (KYECAssyShippingInfo) iterator.next();

               lotNumber    = testShipInfo.getLotNumber() ;
               partNumber   = testShipInfo.getPartNumber();
               fabLotNumber = testShipInfo.getFablotNumber();
               nextLocation = testShipInfo.getShipLocation();
               String shipDate = null;

               if ( testShipInfo.getShipDate() != null )
               {
                   shipDate = StringUtils.formatDate( testShipInfo.getShipDate(), "yyyy/MM/dd", "MM/dd/yyyy");
               }

               if ( lotNumber != null && partNumber != null && fabLotNumber != null )
               {
                   testShippedLot = ( ShippedLot ) m_fgshipDataMap.get ( partNumber + lotNumber + fabLotNumber + nextLocation + shipDate );

                   if ( testShippedLot == null )
                   {
                        testShippedLot = new ShippedLot( VENDOR_NAME_KYEC, LOCATION_TYPE_FINISHED_GOODS );
                        m_fgshipDataMap.put( partNumber + lotNumber + fabLotNumber + nextLocation + shipDate, testShippedLot );
                   }

                   int quantity = 0;
                   if ( testShippedLot.getShipQty() != null )
                   {
                       try
                       {
                           quantity = Integer.parseInt( testShippedLot.getShipQty() );
                       }
                       catch ( NumberFormatException ignore )
                       {
                           quantity = 0;
                       }
                       try
                       {
                           quantity += Integer.parseInt( testShipInfo.getOutputQty() );
                       }
                       catch ( NumberFormatException ignore )
                       {
                           quantity = 0;
                       }
                   }
                   else
                   {
                       try
                       {
                           quantity = Integer.parseInt( testShipInfo.getOutputQty() );
                       }
                       catch ( NumberFormatException ignore )
                       {
                           quantity = 0;
                       }
                   }

                   if ( quantity > 0 )
                   {
                       testShippedLot.setShippingDoc( testShipInfo.getShippingNo() );
                       testShippedLot.setLotNumber( lotNumber );
                       testShippedLot.setPartNumber( partNumber );
                       testShippedLot.setShipDate( shipDate );
                       testShippedLot.setShipQty( quantity + "" );
                       testShippedLot.setCustomerPO( testShipInfo.getPoNo() );
                       testShippedLot.setCustomerWO( testShipInfo.getWoNo() );
                       testShippedLot.setPackageType( testShipInfo.getPkgType() );
                       testShippedLot.setTestProgram( testShipInfo.getCpTestPgm() );
                       testShippedLot.setInvoiceNumber( testShipInfo.getInvoiceNo() );
                       testShippedLot.setNextLocation( nextLocation );
                       testShippedLot.setFabLotNumber( fabLotNumber );
                   }
               }
           }
       }
        catch(Exception e )
        {
            e.printStackTrace();
            log("Exception while geting KYEC FG Shipping inforamtion" + e);
            throw  e;
        }
    }
    */
    private void log( String message )
    {
      if ( message == null ) return;

      if ( m_parserLogger != null )
      {
          m_parserLogger.logDebug( message + LINE_SEPARATOR );
      }
      else
      {
          System.out.println( message );
      }
    } // end of log method

}
